package com.zyb.beiojbackendjudgeservice.strategy;

import cn.hutool.json.JSONUtil;
import com.zyb.beiojmodel.model.codesandbox.ExecuteCodeResponse;
import com.zyb.beiojmodel.model.codesandbox.QuestionJudgeInfo;
import com.zyb.beiojmodel.model.dto.question.QuestionJudgeCase;
import com.zyb.beiojmodel.model.dto.question.QuestionJudgeConfig;
import com.zyb.beiojmodel.model.entity.Question;
import com.zyb.beiojmodel.model.enums.JudgeInfoMessageEnum;


import java.util.List;

/**
 * @author 十八岁讨厌编程
 * @date 2025/2/11 11:38
 * @PROJECT_NAME beioj-backend
 * @description
 */

public class JavaJudgeStrategy implements JudgeStrategy{

    @Override
    public QuestionJudgeInfo doJudge(StrategyContext strategyContext) {
        ExecuteCodeResponse executeCodeResponse = strategyContext.getExecuteCodeResponse();
        List<QuestionJudgeCase> questionJudgeCaseList = strategyContext.getQuestionJudgeCaseList();
        Question question = strategyContext.getQuestion();


        //● 根据沙箱的执行结果，设置题目的判题状态和信息
        JudgeInfoMessageEnum judgeInfoMessageEnum = JudgeInfoMessageEnum.WAITING;
        List<String> outputListReturn = executeCodeResponse.getOutputList();
        QuestionJudgeInfo judgeInfoReturn = executeCodeResponse.getJudgeInfo();

        //构造返回体
        Long time = judgeInfoReturn.getTime();
        Long memory = judgeInfoReturn.getMemory();
        QuestionJudgeInfo questionJudgeInfo = new QuestionJudgeInfo();
        questionJudgeInfo.setTime(time);
        questionJudgeInfo.setMemory(memory);


        //判断逻辑：
        //● 先判断沙箱执行的结果输出是否和预期的输出数量相等
        if (outputListReturn.size() != questionJudgeCaseList.size()) {
            judgeInfoMessageEnum = JudgeInfoMessageEnum.WRONG_ANSWER;
            questionJudgeInfo.setMessage(judgeInfoMessageEnum.getValue());
            return questionJudgeInfo;
        }
        //● 一次判断每一项输出和预期输出是否相等
        for (int i = 0; i < questionJudgeCaseList.size(); i++) {
            if (!questionJudgeCaseList.get(i).getOutput().toString().equals(outputListReturn.get(i))) {
                judgeInfoMessageEnum = JudgeInfoMessageEnum.WRONG_ANSWER;
                questionJudgeInfo.setMessage(judgeInfoMessageEnum.getValue());
                return questionJudgeInfo;
            }

        }
        //● 判断题目的限制是否符合要求（也就是judgeInfo中的信息是否满足judgeConfig中规定的）

        QuestionJudgeConfig questionRequire = JSONUtil.toBean(question.getJudgeConfig(), QuestionJudgeConfig.class);
        //假设java代码套多执行5s
        final long JAVA_EXTARTIME = 5;
        if (time - JAVA_EXTARTIME > questionRequire.getTimeLimit()) {
            judgeInfoMessageEnum = JudgeInfoMessageEnum.TIME_LIMIT_EXCEEDED;
            questionJudgeInfo.setMessage(judgeInfoMessageEnum.getValue());
            return questionJudgeInfo;
        }
        if (memory > questionRequire.getMemoryLimit()) {
            judgeInfoMessageEnum = JudgeInfoMessageEnum.MEMORY_LIMIT_EXCEEDED;
            questionJudgeInfo.setMessage(judgeInfoMessageEnum.getValue());
            return questionJudgeInfo;
        }
        //● 可能还有其他的异常情况
        judgeInfoMessageEnum = JudgeInfoMessageEnum.ACCEPTED;
        questionJudgeInfo.setMessage(judgeInfoMessageEnum.getValue());
        return questionJudgeInfo;
    }
}
